ОБЯЗАТЕЛЬНОДЛЯ НОВИЧКОВНЕ ДЛЯ НОВИЧКОВВ РАЗРАБОТКЕ
Всем
Справочник по HTTP
🔹 HTTP-методы (RFC 9110, Section 9)
| Метод | Описание | Безопасность | Идемпотентность | Кэшируемость | Основные заголовки, связанные с методом |
|---|
GET | Запрос ресурса по URI. Не должен изменять состояние сервера. | Да | Да | Да (Cache-Control, Expires, ETag, Vary) | If-None-Match, If-Modified-Since, Range, Accept-* |
HEAD | Как GET, но без тела ответа. Используется для получения метаданных. | Да | Да | Да (как GET) | Те же, что для GET |
POST | Отправка данных для обработки (создание, инициирование действия). | Нет | Нет (обычно) | Нет (по умолчанию; кэширование возможно при явном указании валидных Cache-Control/Expires и 200/201/304 — но практика редка) | Content-Type, Content-Length, Expect: 100-continue, Transfer-Encoding |
PUT | Замена ресурса по URI. Полная замена. | Нет | Да | Нет (200/201/204 могут кэшироваться при Cache-Control: public) | Content-Type, If-Match, If-Unmodified-Since, Content-Range (не для частичной замены — это PATCH) |
DELETE | Удаление ресурса. | Нет | Да | Нет (200/202/204 — возможно кэширование при явных директивах) | If-Match, If-Unmodified-Since |
PATCH | Частичное обновление ресурса. Тело — patch-документ (RFC 5789, JSON Patch, XML Patch и др.). | Нет | Нет (если сервер не гарантирует идемпотентность патча) | Нет | Content-Type (должен быть application/json-patch+json, application/merge-patch+json, application/xml-patch+xml и т.п.), If-Match |
OPTIONS | Запрос поддерживаемых методов по URI или сервером (если *). | Да | Да | Нет | Allow в ответе |
TRACE | Эхо-запрос для диагностики пути запроса. | Да | Да | Нет | Max-Forwards (должен быть ≥ 0), Via |
CONNECT | Установка туннеля к серверу (для HTTPS через прокси). | Нет | Нет | Нет | Используется на уровне соединения; не имеет тела в запросе/ответе (кроме ошибок) |
Примечания:
- Безопасность — не изменяет состояние сервера (по RFC: does not alter the state of the server).
- Идемпотентность — повторный вызов с теми же параметрами даёт тот же результат (не обязательно тот же ответ:
200 vs 204 допустимо, если состояние не изменилось).
- Кэшируемость — только ответы
200, 203, 204, 206, 300, 301, 308, 404, 405, 410, 414, 501 могут быть кэшированы по умолчанию (RFC 9111, Section 4.2.2); остальные — только при явных Cache-Control/Expires.
- Дополнительные методы:
LINK, UNLINK (устарели, не в RFC); SEARCH (WebDAV, RFC 5323); REPORT (WebDAV, DAV SEARCH); MKCOL, COPY, MOVE, LOCK, UNLOCK (WebDAV, RFC 4918); BIND, REBIND, UNBIND (WebDAV, RFC 5842); ACL (WebDAV, RFC 3744); PROPFIND, PROPPATCH (WebDAV, RFC 4918); BASELINE-CONTROL, CHECKIN, CHECKOUT, MERGE, MKACTIVITY, MKWORKSPACE, UPDATE, VERSION-CONTROL (DeltaV, RFC 3253). Большинство из них не поддерживаются в общих фреймворках, но могут встречаться в специализированных системах (CMS, CMS, DMS).
🔹 Статус-коды (RFC 9110, Sections 15–17)
Класс 1xx: Информационные (не завершают запрос)
| Код | Название | Пояснение | Особенности |
|---|
100 | Continue | Сервер получил заголовки, клиент может отправлять тело. | Используется при Expect: 100-continue. Сервер не должен отправлять 100, если не получал Expect: 100-continue. |
101 | Switching Protocols | Сервер согласен перейти на протокол, указанный в Upgrade. | Обязательна заголовок Upgrade и Connection: upgrade. Пример: переход на WebSocket (Upgrade: websocket). |
102 | Processing (WebDAV, RFC 2518) | Сервер принял запрос, но ещё не завершил обработку. | Предотвращает таймауты у клиента при долгих операциях. |
103 | Early Hints (RFC 8297) | Промежуточный ответ с заголовками (например, Link: </style.css>; rel=preload), до формирования полного ответа. | Позволяет браузеру начать предзагрузку ресурсов. Поддержка: Chrome ≥69, Firefox ≥72. |
104–199 | — | Зарезервированы для будущего использования. | Никогда не должны использоваться. |
Класс 2xx: Успешные
| Код | Название | Пояснение | Особенности |
|---|
200 | OK | Запрос успешен. Тело — ресурс или результат. | Самый распространённый код. Для HEAD — только заголовки. |
201 | Created | Ресурс создан. | Обязателен Location с URI нового ресурса (если известен). Подходит для POST/PUT. |
202 | Accepted | Запрос принят, но обработка не завершена (асинхронная обработка). | Ответ не должен содержать результат; может включать ссылку на статус (Location, Content-Location, Link). |
203 | Non-Authoritative Information | Ответ получен из кэша или промежуточного узла, и информация может отличаться от исходной. | Редко используется. Кэшируем. |
204 | No Content | Успешно, но без тела. | Обязательно Content-Length: 0 или отсутствие тела (Transfer-Encoding не должен быть chunked). Подходит для DELETE, PATCH, POST без ответа. |
205 | Reset Content | Клиент должен сбросить документ (например, очистить форму). | Не имеет тела. Редко поддерживается браузерами. |
206 | Partial Content | Ответ на Range-запрос. | Обязательны Content-Range, Content-Length (длина части), Accept-Ranges: bytes. Заголовок Content-Type должен быть таким же, как у полного ресурса. |
207 | Multi-Status (WebDAV, RFC 4918) | Множественные статусы в теле (XML). | Используется в WebDAV-операциях (PROPFIND, LOCK). |
208 | Already Reported (WebDAV, RFC 5842) | Ресурс уже включён в предыдущий 207. | Для избежания дублирования в древовидных запросах. |
226 | IM Used (RFC 3229) | Ответ — дельта от предыдущего (If-None-Match, A-IM). | A-IM (Accept Instance Manipulations) — устаревший, почти не используется. |
Класс 3xx: Перенаправления
| Код | Название | Пояснение | Особенности |
|---|
300 | Multiple Choices | Несколько вариантов представления. | Редко используется. Может возвращать список (HTML, XML). Кэшируем. |
301 | Moved Permanently | Ресурс перемещён навсегда. | Кэшируем. Браузеры изменяют метод POST → GET при редиректе (RFC не обязывает, но практика такова). |
302 | Found (ранее Moved Temporarily) | Временное перенаправление. | Не должен кэшироваться без Cache-Control/Expires. Браузеры также меняют POST → GET. |
303 | See Other | Ответ доступен по другому URI, и должен быть запрошен через GET. | Явно требует смены метода на GET. Используется после POST для предотвращения повторной отправки. |
304 | Not Modified | Ресурс не изменился (If-None-Match, If-Modified-Since). | Без тела. Должен включать кэш-валидирующие заголовки (ETag, Last-Modified, Cache-Control, Expires, Vary). |
305 | Use Proxy (устарел, RFC 7231) | — | Не использовать. Уязвимость (раскрытие прокси). |
306 | (зарезервирован) | — | Никогда не использовался. |
307 | Temporary Redirect | Временное перенаправление с сохранением метода и тела. | Отличие от 302: клиент не должен менять POST → GET. |
308 | Permanent Redirect | Постоянное перенаправление с сохранением метода и тела. | Отличие от 301: клиент не должен менять POST → GET. |
Класс 4xx: Ошибки клиента
(Запрос некорректен или не может быть выполнен. Сервер понял запрос, но отказывается его исполнить.)
| Код | Название | RFC / Источник | Пояснение | Особенности, нюансы и практика |
|---|
400 | Bad Request | RFC 9110 | Синтаксическая ошибка в запросе (невалидный JSON, нарушение формата URI, неправильные заголовки и т.п.). | Универсальный код при отсутствии более точного. Не следует использовать, если есть более специфичный (404, 405, 415, 422). Тело должно объяснять ошибку (например, application/problem+json). |
401 | Unauthorized | RFC 9110 | Отсутствует или недействителен механизм аутентификации (WWW-Authenticate обязателен в ответе). | Не путать с 403. Требует аутентификации (например, Basic, Bearer). Может быть вызвано отсутствием заголовка Authorization, просроченным токеном, неправильным realm. |
402 | Payment Required | RFC 9110 | Зарезервирован для будущего использования (платёжные системы). | Де-факто используется некоторыми SaaS для «trial expired». Не стандартизирован. |
403 | Forbidden | RFC 9110 | Доступ запрещён даже при успешной аутентификации (недостаточно прав, IP в чёрном списке, политики безопасности). | Сервер не обязан раскрывать причину (404 иногда используется вместо 403 для сокрытия существования ресурса — security through obscurity). |
404 | Not Found | RFC 9110 | Ресурс по указанному URI не найден. | Кэшируем. Может быть возвращён и при 403 по соображениям безопасности. |
405 | Method Not Allowed | RFC 9110 | Метод не поддерживается для данного URI. | Обязательный заголовок Allow в ответе (список допустимых методов, например: GET, HEAD, OPTIONS). |
406 | Not Acceptable | RFC 9110 | Сервер не может сгенерировать ответ, удовлетворяющий Accept-* заголовкам клиента. | Редко используется (чаще возвращают 200 с наилучшим из доступного или 400). |
407 | Proxy Authentication Required | RFC 9110 | Аутентификация требуется на уровне прокси. | Аналог 401, но для прокси. Обязателен заголовок Proxy-Authenticate. |
408 | Request Timeout | RFC 9110 | Сервер не дождался полного запроса (например, не дождался тела при Content-Length > 0). | Может быть отправлен даже после частичного получения тела. Не означает, что тело не было отправлено — только что сервер отказался ждать. |
409 | Conflict | RFC 9110 | Запрос конфликтует с текущим состоянием ресурса (например, уникальное ограничение БД, состояние «уже забронировано»). | Тело должно содержать информацию о природе конфликта. |
410 | Gone | RFC 9110 | Ресурс намеренно и постоянно удалён; нет перенаправления. | Кэшируем. Отличается от 404 тем, что сервер знает, что ресурс больше не будет доступен. |
411 | Length Required | RFC 9110 | Требуется заголовок Content-Length, так как сервер не поддерживает Transfer-Encoding: chunked. | Актуален для очень старых серверов или специфичных API. Современные серверы почти всегда поддерживают chunked. |
412 | Precondition Failed | RFC 9110 | Условие в If-* заголовках (If-Match, If-Unmodified-Since) не выполнено. | Используется для optimistic concurrency control (ETag, Last-Modified). |
413 | Payload Too Large | RFC 9110 | Тело запроса превышает лимит сервера. | Может сопровождаться заголовком Retry-After, если перегрузка временная. Ранее назывался Request Entity Too Large. |
414 | URI Too Long | RFC 9110 | URI превышает допустимую длину сервера. | Часто возникает при GET с длинной query string (лучше использовать POST). Кэшируем. |
415 | Unsupported Media Type | RFC 9110 | Content-Type в запросе не поддерживается сервером. | Аналог 406, но для тела запроса. Пример: отправка application/xml, если API принимает только application/json. |
416 | Range Not Satisfiable | RFC 9110 | Диапазон в Range недопустим (например, bytes=500-499, bytes=9999-, если ресурс короче). | Обязательный заголовок Content-Range: */длина_ресурса. |
417 | Expectation Failed | RFC 9110 | Сервер не может удовлетворить условие в Expect (например, Expect: 100-continue при невозможности выполнить). | Редко встречается — большинство серверов просто игнорируют Expect, если не поддерживают. |
418 | I’m a teapot | RFC 2324 (HTTP Easter Eggs), RFC 7168 | Шуточный код из Hyper Text Coffee Pot Control Protocol (HTCPCP). | Возвращается некоторыми серверами (например, Cloudflare) при 418-запросе как Easter Egg. Не для production. |
421 | Misdirected Request | RFC 9112 (HTTP/2) | Запрос направлен на хост/порт, не способный его обработать (например, HTTP/2 connection coalescing с разными сертификатами). | Сервер должен закрыть соединение после отправки. |
422 | Unprocessable Content | RFC 9110 (ранее RFC 4918 WebDAV) | Синтаксис тела корректен, но семантика недопустима (например, валидный JSON, но email не соответствует формату). | Предпочтителен перед 400 при валидации бизнес-логики. |
423 | Locked | RFC 4918 (WebDAV) | Целевой ресурс заблокирован. | Используется в WebDAV (LOCK). Может указывать на Lock-Token в заголовке. |
424 | Failed Dependency | RFC 4918 (WebDAV) | Операция не выполнена из-за неудачи в зависимом запросе (например, в 207 Multi-Status). | Только в WebDAV. |
425 | Too Early | RFC 8470 | Сервер отказывается обрабатывать запрос из-за риска повторной отправки (например, при Early Data в TLS 1.3 без подтверждения handshake). | Связан с Early-Data: 1. Клиент должен повторить без early data. |
426 | Upgrade Required | RFC 9110 | Сервер требует обновления протокола (например, с HTTP/1.0 на HTTP/1.1). | Обязательные заголовки: Upgrade, Connection: upgrade. |
428 | Precondition Required | RFC 6585 | Сервер требует условных заголовков (If-Match или If-Unmodified-Since) для предотвращения «lost update». | Используется при optimistic locking. Сервер отказывается служить без ETag-проверки. |
429 | Too Many Requests | RFC 6585 | Превышен лимит запросов (rate limiting). | Рекомендуется Retry-After. Может сопровождаться X-RateLimit-* заголовками (не стандартизированы). Пример: X-RateLimit-Limit, X-RateLimit-Remaining, X-RateLimit-Reset. |
431 | Request Header Fields Too Large | RFC 6585 | Заголовки запроса слишком велики (например, длинный Cookie, Authorization). | Может возникать при атаке через увеличение размера заголовков. |
451 | Unavailable For Legal Reasons | RFC 7725 | Доступ запрещён по юридическим причинам (цензура, блокировка по решению суда). | Обязательный Link с rel="blocked-by" и URI органа, потребовавшего блокировку. |
Примечания по практике:
- Коды
400, 403, 404, 422, 429 — наиболее частые в REST API.
- Коды
418, 419 (Laravel-specific «Session Expired»), 420 (Twitter устаревший «Enhance Your Calm»), 430 (Cloudflare — «Request Header Fields Too Large» альтернатива 431) — не стандартизированы, но встречаются.
499 (Nginx: «Client Closed Request») — клиент разорвал соединение до получения ответа. Полезен для логирования и мониторинга.
Класс 5xx: Ошибки сервера
(Сервер не смог обработать корректный запрос.)
| Код | Название | RFC / Источник | Пояснение | Особенности и распространённые причины |
|---|
500 | Internal Server Error | RFC 9110 | Общая ошибка сервера (необработанное исключение, ошибка в коде). | Универсальный код при отсутствии более точного. Должен сопровождаться логированием. Избегать возвращения stack trace в production. |
501 | Not Implemented | RFC 9110 | Метод или функциональность не реализована на сервере. | Аналог 405, но на уровне функциональности, а не URI. Кэшируем. |
502 | Bad Gateway | RFC 9110 | Сервер (шлюз/прокси) получил недопустимый ответ от вышестоящего сервера. | Часто при падении upstream (API, БД, микросервис). Nginx, Cloudflare возвращают при upstream prematurely closed connection. |
503 | Service Unavailable | RFC 9110 | Сервер временно недоступен (перегрузка, обслуживание). | Желательно Retry-After. Кэшируется только при явных директивах. Отличается от 502: проблема на самом сервере, а не в upstream. |
504 | Gateway Timeout | RFC 9110 | Шлюз/прокси не дождался ответа от upstream. | Аналог 408, но на уровне прокси. Часто при долгих запросах к БД или внешним API. |
505 | HTTP Version Not Supported | RFC 9110 | Версия HTTP в строке запроса не поддерживается. | Например, HTTP/3.0 при поддержке только HTTP/1.1 и HTTP/2. |
506 | Variant Also Negotiates | RFC 2295 | Циклическая ссылка в контентной неготиации (Alternates). | Экзотично; почти не встречается. |
507 | Insufficient Storage | RFC 4918 (WebDAV) | Недостаточно места для выполнения операции (например, загрузка). | Используется в WebDAV и некоторых облачных API. |
508 | Loop Detected | RFC 5842 (WebDAV) | Обнаружен бесконечный цикл (например, в 207 Multi-Status с рекурсией). | Только WebDAV. |
509 | Bandwidth Limit Exceeded | Не стандартизирован (cPanel) | Превышен лимит трафика. | Встречается в хостингах (cPanel). |
510 | Not Extended | RFC 2774 | Сервер требует расширения (Mandatory заголовки), которое клиент не предоставил. | Устаревшее; не поддерживается. |
511 | Network Authentication Required | RFC 6585 | Требуется аутентификация в сети (например, captive portal). | Браузер должен открыть окно с формой (например, Wi-Fi логин). В ответе — HTML-страница с формой. |
520–599 | — | Cloudflare, AWS, Fastly | Нестандартные коды операторов CDN/облаков. | Примеры: |
520 Unknown Error (Cloudflare)
521 Web Server Is Down (Cloudflare)
522 Connection Timed Out (Cloudflare)
523 Origin Is Unreachable (Cloudflare)
524 A Timeout Occurred (Cloudflare)
525 SSL Handshake Failed (Cloudflare)
526 Invalid SSL Certificate (Cloudflare)
527 Railgun Error (Cloudflare)
530 Origin Error / 1.1.1.1 Error (Cloudflare)
561 Unauthorized (AWS ALB — при аутентификации через Cognito, если токен недействителен)
Уточняйте документацию CDN/облака.
Примечания:
500 должен быть финальным резервом. Стремитесь к более точным кодам (502, 503, 504, 507).
- В микросервисах
502/504 — сигнал о проблемах в сети или upstream’ах; 500 — о проблемах в самом сервисе.
- Избегайте
500 при валидации входных данных — это 4xx.
🔹 Заголовки HTTP
Классификация по назначению (RFC 9110, RFC 9112, RFC 9113, RFC 9114, IETF drafts, WHATWG, W3C).
1. Общие заголовки (могут быть в запросе и ответе)
| Заголовок | Описание | Синтаксис | Примечания |
|---|
Cache-Control | Директивы кэширования. | token [ "=" ( token / quoted-string ) ] *( OWS ";" OWS token [ "=" ( token / quoted-string ) ] ) | Основные директивы: |
Запрос: max-age, max-stale, min-fresh, no-cache, no-store, only-if-cached
Ответ: max-age, s-maxage, public, private, no-cache, no-store, must-revalidate, proxy-revalidate, immutable, stale-while-revalidate, stale-if-error (RFC 5861), no-transform
Приоритет: s-maxage > max-age > Expires. |
| Connection | Управление соединением. | token *( OWS "," OWS token ) | keep-alive, close, upgrade. Для HTTP/2+ игнорируется, кроме upgrade (для 101 Switching Protocols). |
| Date | Дата и время формирования сообщения. | HTTP-date (RFC 9110, Section 5.6.7) | Обязателен в ответах, кроме 5xx. Формат: Sun, 06 Nov 1994 08:49:37 GMT. |
| Pragma | Совместимость с HTTP/1.0. | token [ "=" ( token / quoted-string ) ] | Pragma: no-cache ≡ Cache-Control: no-cache в HTTP/1.0. Устарел. Игнорируется при наличии Cache-Control. |
| Trailer | Имена заголовков в трейлере (при Transfer-Encoding: chunked). | field-name *( OWS "," OWS field-name ) | Заголовки, которые будут в конце тела (после 0\r\n). Например, Trailer: Server-Timing. |
| Transfer-Encoding | Кодировка тела. | token *( OWS "," OWS token ) | chunked, compress, deflate, gzip, identity. Последний transfer-coding должен быть chunked или identity. Для HTTP/2+ не используется (тело всегда в frame’ах). |
| Upgrade | Предложение смены протокола. | token *( "/" token *( ";" token [ "=" ( token / quoted-string ) ] ) ) *( OWS "," OWS ... ) | Пример: Upgrade: websocket, Upgrade: h2c, websocket. Обязательно с Connection: upgrade. |
| Via | Цепочка прокси/шлюзов. | *( "," OWS ) ( received-protocol RWS host [ ":" port ] ) | Пример: Via: 1.1 proxy1, 1.1 proxy2 (Apache). Полезно для диагностики. |
1. Управление содержимым и согласованием (Accept-*)
| Заголовок | RFC | Синтаксис | Пояснение | Особенности и практика |
|---|
Accept | RFC 9110, 12.5.1 | media-range *( OWS ";" OWS "q" "=" qvalue ) *( OWS "," OWS media-range ... ) media-range = type "/" subtype *( OWS ";" OWS parameter ) | Предпочтения клиента по Content-Type ответа. | Пример: Accept: text/html, application/xhtml+xml;q=0.9, application/xml;q=0.8, */*;q=0.7 — q=1.0 по умолчанию. — Сервер не обязан следовать; может вернуть 406 при невозможности. — */* — любые типы. — Приоритет: точное совпадение > type/* > */*. |
Accept-Charset | RFC 9110, 12.5.2 | token *( OWS ";" OWS "q" "=" qvalue ) *( OWS "," OWS token ... ) | Предпочтения по кодировкам символов (charset). | Пример: Accept-Charset: utf-8, iso-8859-1;q=0.5. Устарел в пользу UTF-8 everywhere. Современные API игнорируют. |
Accept-Encoding | RFC 9110, 12.5.3 | token *( OWS ";" OWS "q" "=" qvalue ) *( OWS "," OWS token ... ) | Поддерживаемые кодировки сжатия (gzip, br, deflate, zstd, identity). | Пример: Accept-Encoding: gzip, br;q=0.8, identity;q=0.5 — identity = без сжатия. — * = любая (редко). — q=0 = не поддерживается. — br требует TLS (в целях совместимости). |
Accept-Language | RFC 9110, 12.5.4 | language-range *( OWS ";" OWS "q" "=" qvalue ) *( OWS "," OWS language-range ... ) language-range = ( 1*8ALPHA *( "-" 1*8ALPHA ) ) / "*" | Языковые предпочтения (ru-RU, en-US, fr). | Пример: Accept-Language: ru-RU, ru;q=0.9, en-US;q=0.8, en;q=0.7 — q=1.0 по умолчанию. — Сервер может использовать для Content-Language, локализации ответа. — Vary: Accept-Language обязателен при разных версиях под язык. |
Content-Type | RFC 9110, 8.3.1 | media-type [ OWS ";" OWS parameter ] *( OWS ";" OWS parameter ) | Тип содержимого тела запроса. | Обязателен при POST/PUT/PATCH с телом. Примеры: application/json application/x-www-form-urlencoded multipart/form-data; boundary=----WebKitFormBoundary7MA4YWxkTrZu0gW — Для multipart обязателен параметр boundary. — charset рекомендуется явно (например, application/json; charset=utf-8). |
Примечание по Vary: Если сервер выдаёт разные ответы на основе Accept-*, обязательно должен возвращать Vary: Accept, Accept-Encoding, Accept-Language и т.д., иначе кэши (CDN, браузеры) могут отдать неправильную версию.
2. Условные запросы (If-*)
| Заголовок | RFC | Синтаксис | Пояснение | Особенности |
|---|
If-Match | RFC 9110, 13.1.1 | "*" / ( entity-tag *( OWS "," OWS entity-tag ) ) | Выполнить, только если ETag ресурса соответствует одному из указанных. | — * = ресурс должен существовать. — Используется для optimistic concurrency: клиент отправляет ETag из предыдущего GET, сервер проверяет. — При несовпадении — 412 Precondition Failed. |
If-None-Match | RFC 9110, 13.1.2 | "*" / ( entity-tag *( OWS "," OWS entity-tag ) ) | Выполнить, только если ETag не совпадает ни с одним из указанных. | — Основной заголовок для кэш-валидации. — При совпадении — 304 Not Modified (для GET/HEAD), 412 (для PUT/DELETE). — * = выполнить, только если ресурс не существует (редко). |
If-Modified-Since | RFC 9110, 13.1.3 | HTTP-date | Выполнить, только если ресурс изменён после указанной даты. | — Используется в паре с Last-Modified. — Менее надёжен, чем ETag (модификация без изменения содержимого). — Игнорируется, если присутствует If-None-Match. |
If-Unmodified-Since | RFC 9110, 13.1.4 | HTTP-date | Выполнить, только если ресурс не был изменён после даты. | — Для optimistic concurrency (альтернатива If-Match). — При нарушении — 412. |
If-Range | RFC 9110, 14.2.4 | entity-tag / HTTP-date | Применить Range, только если ресурс не изменился (по ETag или Last-Modified). | — Используется при частичных загрузках: если ресурс изменился, сервер возвращает 200 с полным телом, а не 206. — Если указан entity-tag, Last-Modified игнорируется. |
Примечание:
- Приоритет:
If-Match > If-Unmodified-Since; If-None-Match > If-Modified-Since.
If-None-Match и If-Modified-Since могут использоваться одновременно — тогда условие ИЛИ (достаточно выполнения одного).
ETag должен быть слабым (W/"...") или сильным ("..."); weak подходит для If-None-Match, strong — для If-Match.
3. Диапазоны и частичная передача
| Заголовок | RFC | Синтаксис | Пояснение |
|---|
Range | RFC 9110, 14.2 | bytes-unit "=" byte-ranges-spec byte-ranges-spec = *( "," OWS ) ( range / suffix-byte-range-spec ) *( OWS "," ... ) range = first-byte-pos "-" [ last-byte-pos ] suffix-byte-range-spec = "-" suffix-length | Запрос части ресурса. |
TE | RFC 9110, 10.1.4 | t-codings *( OWS "," OWS t-codings ) t-codings = "trailers" / ( transfer-coding [ OWS ";" OWS "q" "=" qvalue ] ) | Поддерживаемые кодировки для трейлеров и тела. |
4. Кэширование (в запросе)
| Заголовок | RFC | Синтаксис | Пояснение |
|---|
Cache-Control (в запросе) | RFC 9110, 5.2 | См. выше | Директивы от клиента к кэшу. |
5. Аутентификация и авторизация
| Заголовок | RFC | Синтаксис | Пояснение | Поддерживаемые схемы |
|---|
Authorization | RFC 9110, 11.6.2 | credentials credentials = auth-scheme [ 1*SP ( token68 / #auth-param ) ] auth-param = token "=" ( token / quoted-string ) | Учётные данные для доступа к ресурсу. | |
Basic: Basic base64("user:pass")
Bearer: Bearer <token> (OAuth 2.0)
Digest: Digest username="...", realm="...", nonce="...", uri="...", response="..."
AWS4-HMAC-SHA256: AWS4-HMAC-SHA256 Credential=..., SignedHeaders=..., Signature=...
Mutual: для Mutual TLS auth (редко)
Hawk, SCRAM, vapid (для WebPush) — специфичные.
— Пространства имён: token68 — base64url без padding (например, JWT).
— Заголовок не шифруется — требует HTTPS. |
| Заголовок | RFC | Синтаксис | Пояснение |
|---|
Proxy-Authorization | RFC 9110, 11.6.3 | Аналогично Authorization | Для аутентификации на прокси. |
6. Сессии и идентификация
| Заголовок | RFC | Синтаксис | Пояснение | Современные расширения |
|---|
Cookie | RFC 6265 | cookie-string = cookie-pair *( ";" OWS cookie-pair ) cookie-pair = cookie-name "=" cookie-value | Отправка сохранённых Set-Cookie. | |
— Может содержать несколько пар. — cookie-name и cookie-value — токены (ограниченный набор символов; в value допустимы кавычки). — Браузер отправляет только куки, соответствующие Domain, Path, Secure, HttpOnly, SameSite. — Для SameSite=Strict не отправляются в кросс-сайтовых GET (но отправляются в POST из того же origin’а).
Расширения: Cookie: __Host-sessionid=abc; __Secure-token=xyz — префиксы для усиленной безопасности (__Host- требует Secure, Path=/, отсутствие Domain; __Secure- — только Secure). |
7. Соединение и транспорт
| Заголовок | RFC | Синтаксис | Пояснение |
|---|
Expect | RFC 9110, 10.1.1 | token [ OWS "=" OWS token ] *( OWS "," OWS ... ) | Ожидания от сервера перед отправкой тела. |
— Единственное стандартное значение: 100-continue. — Сервер отвечает 100 Continue или 417 Expectation Failed. — Используется для экономии bandwidth при больших телах. |
| Forwarded | RFC 7239 | forwarded-element *( "," OWS forwarded-element ) forwarded-element = [ "by" "=" node ] [ ";" "for" "=" node ] [ ";" "host" "=" host ] [ ";" "proto" "=" proto ] | Стандартная замена X-Forwarded-*. | Пример: Forwarded: for=192.0.2.43, for="[2001:db8:cafe::17]", by=203.0.113.60; proto=https; host=example.com — for — клиент или предыдущий прокси. — by — этот прокси. — proto — исходная схема. — Рекомендуется использовать вместо X-Forwarded-* (если поддерживается). |
| Host | RFC 9110, 7.2 | uri-host [ ":" port ] | Целевой хост и порт (обязателен в HTTP/1.1). | — Без него — 400. — Используется для виртуального хостинга. — В HTTP/2 передаётся как псевдозаголовок :authority. |
| Max-Forwards | RFC 9110, 7.6.2 | 1*DIGIT | Максимальное число прокси для TRACE/OPTIONS. | — Уменьшается на 1 каждым прокси. — При 0 — обрабатывающий узел должен сам ответить. — Только для TRACE, OPTIONS; иначе игнорируется. |
8. Отладка и трассировка
| Заголовок | RFC / Источник | Синтаксис | Пояснение |
|---|
X-Request-ID | Не стандартизирован | token | Уникальный ID запроса для логирования и трассировки. |
— Часто UUIDv4. — Должен проксироваться без изменений. — Используется в Zipkin, Jaeger, OpenTelemetry. |
| X-Correlation-ID | Не стандартизирован | token | ID корреляции для цепочки запросов (например, микросервисы). | Отличие от X-Request-ID: один Correlation-ID — на всю транзакцию, много Request-ID — на каждый вызов. |
| Traceparent | W3C Trace Context | version "-" trace-id "-" parent-id "-" trace-flags | Стандартизованный заголовок для распределённой трассировки. |
— version: 00 — trace-id: 32 hex — parent-id: 16 hex — trace-flags: 01 (sampled), 00 (not sampled) — Обязателен в OpenTelemetry. |
| Tracestate | W3C Trace Context | list-member *( OWS "," OWS list-member ) list-member = key "=" value | Дополнительные данные провайдеров (vendor-specific). |
— key = ( lcalpha / DIGIT / "_" / "-"/ "*" / "/" ) 0*255( lcalpha / DIGIT / "_" / "-"/ "*" / "/" ) — Пример: rojo=00f067aa0ba902b7,congo=t61rcWkgMzE |
9. Безопасность и политики
| Заголовок | RFC / Источник | Синтаксис | Пояснение |
|---|
Origin | RFC 6454 | origin = scheme "://" host [ ":" port ] | Происхождение запроса (для CORS и POST). |
— Отправляется при POST, PUT, DELETE, PATCH, TRACE, CONNECT, и всех CORS-предварительных запросах. — Для GET/HEAD — только при кросс-сайтовом CORS. — null для data:, file:, sandbox’ed iframe’ов. |
| Referer | RFC 9110, 10.1.3 | absolute-URI / partial-URI | URI откуда пришёл запрос. |
— Опечатка в названии (Referrer → Referer) — историческая. — Может быть пустым (например, при переходе с HTTPS на HTTP). — Политики: Referrer-Policy управляет его отправкой. |
| DNT | Не стандартизирован (deprecated) | "1" / "0" | Do Not Track. |
— 1 = не отслеживать. — Игнорируется большинством сервисов. Устарел. |
| Sec-Fetch-* | Fetch Metadata Request Headers | См. ниже | Метаданные о контексте запроса (для защиты от CSRF, XS-Leaks). |
Sec-Fetch-* заголовки (WHATWG Fetch, 2019+)
| Заголовок | Возможные значения | Пояснение |
|---|
Sec-Fetch-Site | cross-site, same-site, same-origin, none | Отношение origin’а запроса и инициатора. |
Sec-Fetch-Mode | navigate, same-origin, no-cors, cors | Режим fetch’а. |
Sec-Fetch-User | ?1 (true) | Запрос инициирован пользователем (клик, submit). |
Sec-Fetch-Dest | document, script, style, image, font, video, audio, worker, embed, object, manifest, empty и др. | Назначение запроса. |
— Отправляются только браузерами (не curl, HttpClient). — Позволяют серверу блокировать подозрительные запросы (например, Sec-Fetch-Dest: script на API-эндпоинте). — Требуют HTTPS (иначе не отправляются).
10. Client Hints (RFC 8942, RFC 8943)
| Заголовок | Тип | Синтаксис | Пояснение |
|---|
Accept-CH | Ответ | token *( OWS "," OWS token ) | Сервер запрашивает у клиента отправку определённых Client Hints. |
Critical-CH | Ответ | Аналогично Accept-CH | Сервер указывает, что эти хинты критичны для корректного ответа. |
Sec-CH-UA | Запрос | list (Structured Fields) | User Agent в структурированной форме. |
Sec-CH-UA-Mobile | Запрос | ?1 / ?0 | Мобильное устройство (?1 = true). |
Sec-CH-UA-Platform | Запрос | string (Structured Fields) | ОС: "Windows", "Android", "macOS", "Linux". |
Sec-CH-UA-Platform-Version | Запрос | string | Версия ОС. |
Sec-CH-UA-Arch | Запрос | string | Архитектура: "x86", "x86_64", "arm", "arm64". |
Sec-CH-UA-Model | Запрос | string | Модель устройства (например, "Pixel 6"). |
Sec-CH-UA-Bitness | Запрос | string | Разрядность: "64", "32". |
Sec-CH-UA-Full-Version-List | Запрос | list | Полные версии (включая патчи). |
DPR | Запрос | sf-decimal | Device Pixel Ratio. |
Viewport-Width | Запрос | sf-integer | Ширина viewport’а в CSS-пикселях. |
Width | Запрос | sf-integer | Желаемая ширина изображения (для img с sizes). |
— Client Hints отправляются только по HTTPS. — Требуют явного согласия через Accept-CH или <meta http-equiv="Accept-CH">. — Используются для адаптивного контента и изображений (<picture>, srcset).
11. Экспериментальные и устаревшие
| Заголовок | Статус | Пояснение |
|---|
X-Forwarded-For | Широко используется (не RFC) | Аналог Forwarded: for=.... |
X-Forwarded-Host | — | Аналог Forwarded: host=.... |
X-Forwarded-Proto | — | Аналог Forwarded: proto=.... |
X-Powered-By | Устаревший | Информация о стеке (PHP/8.2, Express). |
X-AspNet-Version, X-Runtime | — | Специфичные для платформ. |
X-Content-Type-Options | Устаревший (но поддерживается) | nosniff — запрет MIME-sniffing’а. |
X-Frame-Options | Устаревший | DENY, SAMEORIGIN, ALLOW-FROM uri |
X-XSS-Protection | Устаревший | 0, 1, 1; mode=block |
Public-Key-Pins | Удалён (2019) | HPKP — уязвимость к DoS. |
1. Управление содержимым
| Заголовок | RFC | Синтаксис | Пояснение | Особенности |
|---|
Content-Type | RFC 9110, 8.3.1 | media-type [ OWS ";" OWS parameter ] *( OWS ";" OWS parameter ) | Тип содержимого тела ответа. | |
— Обязателен при наличии тела (кроме 204, 304). — Примеры: text/html; charset=utf-8 application/json; charset=utf-8 image/jpeg multipart/byteranges; boundary=... (при 206) — Параметр charset рекомендуется явно указывать для текстовых типов. — Для text/* по умолчанию ISO-8859-1; игнорируется, если указан charset. — Браузеры могут выполнять MIME-sniffing, если не указан X-Content-Type-Options: nosniff (устаревший, но эффективный) или если тип text/plain. |
| Content-Length | RFC 9110, 6.3.2 | 1*DIGIT | Длина тела в октетах. |
— Обязателен, если нет Transfer-Encoding: chunked или Content-Range. — Не должен присутствовать при Transfer-Encoding: chunked, 204, 304, 1xx, 204. — При несоответствии поведение неопределено (обрезка/дозагрузка). |
| Content-Encoding | RFC 9110, 8.4 | token *( OWS "," OWS token ) | Кодировки, применённые к телу после Content-Type. |
— Пример: Content-Encoding: gzip — Порядок важен: Content-Encoding: br, gzip = сначала br, потом gzip (редко). — Должен соответствовать Accept-Encoding. — Не для сжатия контента (например, ZIP-файла), а для транспортного сжатия. Для архивов — Content-Type: application/zip. |
| Content-Language | RFC 9110, 8.6 | language-tag *( OWS "," OWS language-tag ) | Язык содержимого. |
— Пример: Content-Language: ru, en — Не влияет на Accept-Language, но может использоваться для Vary. — Для многоязычных документов — перечисление. |
| Content-Location | RFC 9110, 8.7 | absolute-URI / partial-URI | URI, по которому доступно именно это представление. |
— Отличается от Location (редирект) и Content-Location (идентичность). — Может совпадать с запрошенным URI или быть другим (например, canonical URL). — При 201 Created может дублировать Location, но семантически: Location — где создан, Content-Location — где находится текущее представление. |
| Content-Range | RFC 9110, 14.4 | range-unit OWS "/" OWS ( range-resp / "*" ) range-resp = range-unit "=" range "/" complete-length | Диапазон в ответе (для 206). |
— Пример: Content-Range: bytes 200-1000/67589 — При 416: Content-Range: bytes */67589 — * — если длина неизвестна (редко). |
| Content-Disposition | RFC 6266 | disposition-type *( OWS ";" OWS disposition-parm ) disposition-parm = "filename" "=" value / "filename*" "=" ext-value / token "=" value | Как обрабатывать тело (отображать inline или как attachment). |
— Типы: inline (по умолчанию), attachment, form-data (в multipart). — Параметры: filename="report.pdf" — для ASCII filename*=UTF-8''%D0%9E%D1%82%D1%87%D0%B5%D1%82.pdf — RFC 5987, для Unicode — Обязателен при скачивании файлов через <a download>. |
2. Кэширование
| Заголовок | RFC | Синтаксис | Пояснение | Взаимодействия |
|---|
Cache-Control | RFC 9110, 5.2 | См. ранее | Директивы кэширования от сервера. | |
— public: может кэшироваться любым кэшем (включая CDN). — private: только клиентским кэшем (не CDN). — max-age=N: свежесть = N секунд. — s-maxage=N: для shared-кэшей (CDN), приоритет над max-age. — must-revalidate: при устаревании — обязательно валидировать. — stale-while-revalidate=N: можно отдавать устаревший, пока идёт фоновая валидация. — immutable: содержимое никогда не меняется (для статики с хэшем в имени). |
| Expires | RFC 9110, 5.3 | HTTP-date | Абсолютная дата устаревания. |
— Игнорируется при наличии Cache-Control: max-age или s-maxage. — Формат: Wed, 21 Oct 2025 07:28:00 GMT. — Ошибки в формате → Expires игнорируется. |
| ETag | RFC 9110, 8.8.3 | entity-tag entity-tag = [ "W/" ] DQUOTE 1*etagc DQUOTE | Уникальный идентификатор версии ресурса. |
— Strong: "abc" — байт-в-байт идентичность. — Weak: W/"abc" — семантическая эквивалентность. — Должен быть уникальным в пределах URI. — Рекомендуется хэш (SHA-256) или хэш содержимого + timestamp. |
| Last-Modified | RFC 9110, 8.8.2 | HTTP-date | Дата последней модификации. |
— Используется с If-Modified-Since, If-Unmodified-Since. — Менее надёжен, чем ETag (модификация без изменения содержимого). — Сервер должен учитывать точность файловой системы (часто округляется до секунды). |
| Vary | RFC 9110, 12.5.5 | field-name *( OWS "," OWS field-name ) | Заголовки запроса, от которых зависит содержимое ответа. |
— Обязателен, если ответ зависит от Accept, Accept-Encoding, Accept-Language, Origin и т.д. — Пример: Vary: Accept-Encoding, Accept — Vary: * — не кэшировать (редко). |
| Age | RFC 9110, 5.1 | 1*DIGIT | Время в секундах, прошедшее с генерации ответа (в shared-кэше). |
— Устанавливается прокси/CDN. — Age = now - Date. |
| Warning | RFC 9110, 5.5 | warn-code OWS warn-agent OWS warn-text [ OWS warn-date ] | Предупреждения о работе кэша. |
— Пример: 110 anderson/1.3.37 "Response is stale" — Коды: 110 — устаревший, 111 — повторная валидация не удалась, 112 — отсоединение, 199 — прочее. |
3. Аутентификация
| Заголовок | RFC | Синтаксис | Пояснение |
|---|
WWW-Authenticate | RFC 9110, 11.6.1 | challenge *( OWS "," OWS challenge ) challenge = auth-scheme [ 1*SP ( token68 / #auth-param ) ] | Требования к аутентификации (401). |
— Примеры: WWW-Authenticate: Basic realm="Access to staging site" WWW-Authenticate: Bearer realm="example", error="invalid_token", error_description="..." — realm — обязательный параметр для Basic, Digest. — Для Bearer — error, error_description, scope, realm. |
| Proxy-Authenticate | RFC 9110, 11.6.3 | Аналогично WWW-Authenticate | Требования к аутентификации на прокси (407). |
4. Сессии
| Заголовок | RFC | Синтаксис | Пояснение | Атрибуты и расширения |
|---|
Set-Cookie | RFC 6265, RFC 6265bis (draft) | cookie-pair *( ";" OWS cookie-av ) cookie-av = expires-av / max-age-av / domain-av / path-av / secure-av / httponly-av / samesite-av / partitioned-av / priority-av | Установка куки. | |
— cookie-pair = cookie-name "=" cookie-value
— Атрибуты: Expires=Wed, 21 Oct 2025 07:28:00 GMT Max-Age=3600 (приоритет над Expires) Domain=example.com (включает поддомены) Path=/admin Secure — только по HTTPS HttpOnly — недоступен из JS (document.cookie) SameSite=Strict|Lax|None Partitioned (RFC 9645, Chrome ≥118) — изоляция в embed’ах (3PCD) Priority=High|Medium|Low (Chrome-only, устаревает в пользу partitioned) — Безопасные префиксы: __Host- — требует Secure, Path=/, отсутствие Domain __Secure- — требует Secure — SameSite=None требует Secure. |
SameSite подробно:
Strict: не отправляется в кросс-сайтовых запросах вообще.
Lax: отправляется только в «безопасных» кросс-сайтовых GET (ссылки), но не в POST, iframe, img.
None: отправляется всегда (требует Secure).
— По умолчанию (если не указано) — Lax (современные браузеры).
5. Перенаправление и навигация
| Заголовок | RFC | Синтаксис | Пояснение |
|---|
Location | RFC 9110, 10.2.2 | absolute-URI / partial-URI | URI для перенаправления (201, 3xx). |
— Для 201 Created — желательно. — Для 3xx — обязательно. — Может быть относительным (браузер резолвит относительно текущего Host). |
| Refresh | Не RFC (HTML Living Standard) | delta-seconds [ ";" OWS "url" "=" DQUOTE uri DQUOTE ] | Автообновление/редирект на стороне клиента. |
— Пример: Refresh: 5; url=/new-location — Устаревший; использовать <meta http-equiv="refresh"> или 3xx. — Не надёжен (блокируется некоторыми браузерами). |
| Retry-After | RFC 9110, 10.2.3 | HTTP-date / 1*DIGIT | Когда повторить запрос (503, 429, 3xx). |
— Пример: Retry-After: 120 (секунд) или Retry-After: Wed, 21 Oct 2025 08:00:00 GMT — Используется клиентами (браузеры — редко; API-клиенты — да). |
6. Безопасность
| Заголовок | RFC / Источник | Синтаксис | Пояснение | Состояние |
|---|
Strict-Transport-Security | RFC 6797 | max-age=delta-seconds [; includeSubDomains] [; preload] | Принудительное использование HTTPS. | |
— max-age=31536000 — 1 год. — includeSubDomains — для всех поддоменов. — preload — запрос включения в HSTS preload list (Chrome, Firefox). |
| Content-Security-Policy | CSP Level 3 | policy-directive *( ";" OWS policy-directive ) | Ограничения на источники ресурсов. |
— Пример: default-src 'self'; script-src 'self' https://cdn.example.com; object-src 'none' — Директивы: default-src, script-src, style-src, img-src, font-src, connect-src, frame-src, child-src, frame-ancestors, form-action, base-uri, sandbox, report-uri, report-to и др. — frame-ancestors заменяет X-Frame-Options. |
| X-Content-Type-Options | Не RFC (Microsoft) | nosniff | Запрет MIME-sniffing’а. |
— Поддерживается всеми браузерами. — Эффективен для script, style, image (если Content-Type не соответствует ожидаемому — блокировка). |
| Referrer-Policy | Referrer Policy | token *( OWS "," OWS token ) | Управление отправкой Referer. |
— Значения: no-referrer, no-referrer-when-downgrade, origin, origin-when-cross-origin, same-origin, strict-origin, strict-origin-when-cross-origin, unsafe-url. — По умолчанию: strict-origin-when-cross-origin (совр. браузеры). |
| Permissions-Policy | Permissions Policy | directive *( "," OWS directive ) directive = token [ "=" *( token / DQUOTE token *( OWS token ) DQUOTE ) ] | Контроль над API браузера (камера, геолокация и др.). |
— Пример: camera=(), geolocation=(self "https://trusted.com") — Заменяет устаревший Feature-Policy. |
| Cross-Origin-Embedder-Policy | COEP | require-corp / credentialless | Требование CORS для embed’ов (включает SharedArrayBuffer). |
— require-corp: все embed’ы (<script>, <img>, fetch()) должны иметь Cross-Origin-Resource-Policy или CORS headers. — credentialless: анонимные запросы (без кук, TLS client cert). |
| Cross-Origin-Opener-Policy | COOP | unsafe-none / same-origin-allow-popups / same-origin | Изоляция окон (защита от XS-Leaks). |
— same-origin: запрет window.opener для кросс-сайтовых окон. — Требуется для SharedArrayBuffer. |
| Cross-Origin-Resource-Policy | CORP | same-site / same-origin / cross-origin | Ограничение embed’ов на уровне ресурса. |
— same-site: только с того же eTLD+1. — same-origin: только с того же origin’а. — Поддерживается не всеми браузерами. |
| Clear-Site-Data | Clear Site Data | "*" / DQUOTE token *( OWS token ) DQUOTE | Очистка данных сайта. |
— Clear-Site-Data: "cache", "cookies", "storage", "executionContexts" — Используется при logout. |
7. Мониторинг и отладка
| Заголовок | RFC / Источник | Синтаксис | Пояснение |
|---|
Server | RFC 9110, 10.2.4 | product *( OWS "/" OWS product-version ) *( OWS product ... ) | Информация о сервере. |
— Пример: Server: nginx/1.24.0 — Рекомендуется минимизировать или удалять (раскрытие версий — риск). |
| Server-Timing | Server Timing | metric-name [ "=" metric-value ] [ ";" OWS "desc" "=" DQUOTE description DQUOTE ] *( "," ... ) | Метрики производительности. |
— Пример: Server-Timing: db;dur=53, app;dur=120.5, cache;desc="redis" — Отображается в DevTools (Chrome, Firefox). — Используется для RUM (Real User Monitoring). |
| Report-To | Reporting API | JSON-объект (см. RFC 9260) | Конфигурация endpoints для отчётов. |
— Пример: Report-To: { "group": "default", "max_age": 10886400, "endpoints": [{ "url": "https://example.com/reports" }], "include_subdomains": true } — Используется для NEL, CSP, Deprecation и др. |
| NEL | Network Error Logging | JSON-объект | Конфигурация логирования сетевых ошибок. |
— Пример: NEL: { "report_to": "default", "max_age": 10886400, "success_fraction": 0.0, "failure_fraction": 1.0 } |
8. CORS и межсайтовые политики
| Заголовок | RFC | Синтаксис | Пояснение |
|---|
Access-Control-Allow-Origin | RFC 6452 | origin / "*" | Разрешённые origin’ы. |
— * — только если Access-Control-Allow-Credentials: false (по умолчанию). — При credentials: true — только конкретный origin, не *. |
| Access-Control-Allow-Methods | — | method *( OWS "," OWS method ) | Разрешённые методы (для preflight). |
— Пример: GET, POST, PUT — Обязателен в preflight-ответе (204/200). |
| Access-Control-Allow-Headers | — | field-name *( OWS "," OWS field-name ) | Разрешённые заголовки (для preflight). |
— Обязательные: Authorization, Content-Type (если не application/x-www-form-urlencoded, multipart/form-data, text/plain). |
| Access-Control-Allow-Credentials | — | "true" | Разрешение credentials (куки, TLS cert, Authorization). |
— Только true (нет false). — При true — Access-Control-Allow-Origin не может быть *. |
| Access-Control-Max-Age | — | 1*DIGIT | Кэширование preflight-ответа (в секундах). |
— Максимум в браузерах: Chrome — 600, Firefox — 86400. — 0 — не кэшировать. |
| Access-Control-Expose-Headers | — | field-name *( OWS "," OWS field-name ) | Заголовки, доступные в getResponseHeader(). |
— По умолчанию: Cache-Control, Content-Language, Content-Length, Content-Type, Expires, Last-Modified, Pragma. — Для кастомных (X-RateLimit-*) — необходимо указать. |
| Access-Control-Request-Method | — | method | Метод, который будет использован в основном запросе (в preflight). | Только в запросе. |
| Access-Control-Request-Headers | — | field-name *( OWS "," OWS field-name ) | Заголовки, которые будут отправлены в основном запросе. | Только в запросе. |
9. Client Hints и контентная адаптация
| Заголовок | RFC | Синтаксис | Пояснение |
|---|
Accept-CH | RFC 8942 | token *( OWS "," OWS token ) | Запрос Client Hints от клиента. |
Accept-CH-Lifetime | Устаревший (заменён Critical-CH) | 1*DIGIT | Время (в секундах), в течение которого клиент должен отправлять указанные хинты. |
Critical-CH | RFC 8942 | Аналогично Accept-CH | Указание критичности хинтов. |
Variants | RFC 8942 | token "=" variant-value *( OWS "," OWS variant-value ) | Информация о вариантах контента (для прокси). |
Variant-Key | RFC 8942 | token *( OWS "," OWS token ) | Какой вариант был выбран. |
10. Экспериментальные и устаревшие
| Заголовок | Статус | Пояснение |
|---|
P3P | Устаревший | Platform for Privacy Preferences. |
Public-Key-Pins | Удалён | HTTP Public Key Pinning. |
Feature-Policy | Устаревший | Заменён на Permissions-Policy. |
Timing-Allow-Origin | Устаревший | Разрешить доступ к PerformanceTiming. |
🔹 Тело сообщения (Message Body)
Тело присутствует в запросе или ответе, если:
- метод подразумевает тело (
POST, PUT, PATCH, REPORT, и др.), и
- статус-код допускает тело (
2xx, 4xx, 5xx, кроме 204, 304, 1xx), и
- присутствует
Content-Length или Transfer-Encoding: chunked или multipart/byteranges.
Форматы тела и их особенности
| MIME-тип | RFC / Спецификация | Структура | Применение | Особенности |
|---|
application/json | RFC 8259 | UTF-8 JSON (рекомендуется), без BOM | REST API, конфиги, обмен данными | |
— charset в Content-Type не обязателен, но рекомендуется: application/json; charset=utf-8. — Сервер должен проверять Content-Type, а не полагаться на Accept. — Ошибки парсинга → 400 Bad Request. |
| application/x-www-form-urlencoded | WHATWG URL | key=value&key2=value2, application/x-www-form-urlencoded | HTML-формы (method="POST"), OAuth2 application/x-www-form-urlencoded |
— Кодирование: application/x-www-form-urlencoded — аналог encodeURIComponent, но с заменой пробелов на +. — Максимальная длина — ограничена сервером (часто 1–10 МБ). — Не поддерживает двоичные данные. |
| multipart/form-data | RFC 7578 | --boundary, части с Content-Disposition: form-data; name="...", filename="...", Content-Type | Загрузка файлов, смешанные данные |
— Обязателен параметр boundary в Content-Type. — Части могут иметь разные Content-Type. — Поддерживается всеми фреймворками и браузерами. — Для файлов: Content-Disposition: form-data; name="file"; filename="test.pdf". — filename* — RFC 5987 для Unicode. |
| text/plain | RFC 2046 | Произвольный текст | Логи, простые ответы, fetch() с response.text() |
— Браузеры могут применять MIME-sniffing → использовать X-Content-Type-Options: nosniff, если важно. — charset желателен. |
| application/octet-stream | RFC 2046 | Произвольные байты | Бинарные данные без метаданных (резервный тип) |
— По умолчанию для неизвестных типов. — Часто используется для скачивания (с Content-Disposition: attachment). |
| multipart/byteranges | RFC 9110, 14.5 | --boundary, части с Content-Range, Content-Type | Ответ на Range с несколькими диапазонами |
— Сервер вправе игнорировать множественные Range и вернуть 200. — Поддержка в браузерах ограничена. |
| text/event-stream | HTML Living Standard | field: value\n\n, data: ..., id:, event:, retry: | Server-Sent Events (SSE) |
— Только text/event-stream; charset=utf-8. — Должен быть Cache-Control: no-cache. — Соединение держится открытым (Transfer-Encoding: chunked). |
| application/gzip, application/deflate, application/br, application/zstd | Не RFC | Сжатый поток | Передача архивов (не путать с Content-Encoding) |
— Отличается от Content-Encoding: это семантическое сжатие (файл-архив), а не транспортное. — Сервер не распаковывает автоматически. — Пример: Content-Type: application/gzip + Content-Disposition: attachment; filename="data.json.gz". |
| application/xml, application/soap+xml | RFC 7303 | XML | SOAP, WebDAV, legacy API |
— charset желателен. — +xml подтипы получают special treatment в браузерах (XML-парсинг, XSLT). |
| application/pdf, image/*, audio/*, video/* | IANA | Бинарный формат | Документы, медиа |
— Браузеры могут рендерить inline (<embed>, <object>, <video>). — Для Content-Disposition: inline — открытие в браузере; attachment — скачивание. |
Важно:
- Тело не должно присутствовать в
HEAD, 204, 304, 1xx.
- При
Transfer-Encoding: chunked тело разбито на чанки:
[chunk-size in hex]\r\n
[chunk-data]\r\n
...
0\r\n
[trailer headers, if any]\r\n
\r\n
Content-Length и Transfer-Encoding взаимоисключающи (если есть TE: chunked, Content-Length игнорируется).
- Для HTTP/2 и HTTP/3 тело передаётся в
DATA фреймах; Transfer-Encoding: chunked не используется.
🔹 Кодировки и сжатие (Content-Encoding)
| Кодировка | RFC / Спецификация | Алгоритм | Header checksum | Stream format | Поддержка |
|---|
gzip | RFC 1952 | DEFLATE + 10-байтный заголовок + 8-байтный trailer (CRC-32, ISIZE) | CRC-32 | ID1=0x1F, ID2=0x8B, CM=8 (deflate), FLG, MTIME, XFL, OS, [extra], [name], [comment], CRC32, ISIZE | Все браузеры, серверы |
deflate | RFC 1951 | Чистый DEFLATE (без заголовка zlib или gzip) | Нет | Raw DEFLATE stream (RFC 1951) | Нестандартно: многие серверы отправляют zlib-обёрнутый поток (RFC 1950), что вызывает ошибки в IE. Избегать в пользу gzip/br. |
br | RFC 7932 | Brotli (LZ77 + Huffman + контекстное моделирование) | Нет (встроенный в формат) | simple, static, dynamic метаблоки | Chrome ≥49, Firefox ≥44, Node.js ≥10.16 |
zstd | RFC 8878 | Zstandard (Facebook) | XXH64 (опционально) | Frame format: magic, frame header, blocks, optional checksum | Поддержка растёт: Cloudflare, Apache, Nginx ≥1.19.7, Chrome ≥110 (экспериментально) |
compress | Устаревший (LZW) | LZW | Нет | UNIX compress format | Не поддерживается. |
Рекомендации:
- Приоритет клиентского
Accept-Encoding: br, zstd, gzip, deflate.
br даёт на 15–20% лучшее сжатие, чем gzip, при сопоставимой скорости декомпрессии.
zstd — выше скорость сжатия/декомпрессии при сопоставимом с br сжатии.
- Для динамических ответов —
gzip (универсально). Для статики — br + fallback на gzip.
- Не сжимать уже сжатые данные (JPEG, PNG, MP4, ZIP) — увеличит размер.
🔹 Аутентификация: схемы и безопасность
| Схема | RFC / Спецификация | Синтаксис Authorization | Безопасность | Использование |
|---|
Basic | RFC 7617 | Basic base64(user:password) | Низкая (credentials в открытом виде) | Требует HTTPS. Для внутренних API, dev-сред. |
Bearer | RFC 6750 | Bearer <token> | Зависит от токена (JWT, opaque) | OAuth 2.0, OpenID Connect. Токен должен быть краткосрочным, с scope, aud. |
Digest | RFC 7616 | Digest username="...", realm="...", nonce="...", uri="...", response="hash(...)", ... | Средняя (защита от passive sniffing) | Устаревает. Уязвим к MITM и replay (без qop=auth-int). |
AWS4-HMAC-SHA256 | AWS Signature Version 4 | AWS4-HMAC-SHA256 Credential=AKI..., SignedHeaders=host;x-amz-date, Signature=... | Высокая (подпись запроса) | AWS API, совместимые S3-сервисы. |
Hawk | Hawk (Eran Hammer) | Hawk id="...", ts="...", nonce="...", mac="...", ext="..." | Высокая (MAC на основе временной метки) | Устаревает (автор отозвал). |
SCRAM | RFC 5802, RFC 7804 | SCRAM-<alg> data="..." | Высокая (защита от offline-атак) | IMAP, XMPP, PostgreSQL SASL. Редко в HTTP. |
vapid | RFC 8292 | vapid t="...", k="..." | Средняя | Web Push: подписка на уведомления. |
Mutual | RFC 8120 | Mutual ... | Очень высокая (двусторонняя аутентификация) | Японские гос. сервисы. Требует клиентских сертификатов. |
Общие рекомендации:
- Всегда использовать HTTPS.
- Избегать
Basic в production.
- Для
Bearer — валидировать iss, aud, exp, iat, nbf, scope.
- Хранить токены в
HttpOnly, Secure, SameSite=Strict куках (не в localStorage).
- Реализовывать refresh tokens с коротким сроком и rotation.
🔹 Сессии: углублённый разбор Set-Cookie
Атрибуты (RFC 6265bis, Chrome ≥118+)
| Атрибут | Значение | Обязательность | Пояснение |
|---|
Secure | флаг | рекомендуется | Только по HTTPS. Обязателен при SameSite=None. |
HttpOnly | флаг | рекомендуется | Недоступен из JS (document.cookie). Защита от XSS. |
SameSite | Strict | Lax | None | рекомендуется | Контроль кросс-сайтовых отправок. None → требует Secure. |
Path | строка | опционально | По умолчанию — путь запроса (не рекомендуется). Лучше явно /. |
Domain | домен | опционально | По умолчанию — текущий хост (без поддоменов). Domain=example.com → включает *.example.com. |
Max-Age | целое ≥ 0 | рекомендуется | Приоритет над Expires. 0 — удалить. |
Expires | HTTP-date | устаревает | Альтернатива Max-Age. |
Partitioned | флаг | экспериментально | Изоляция куки в embed’ах (3PCD, Chrome ≥118, RFC 9645). Требует __Host- или __Secure-. |
Priority | High | Medium | Low | устаревает | Chrome-only, заменён на Partitioned. |
Безопасные префиксы (RFC 6265bis)
| Префикс | Требования | Цель |
|---|
__Host- | Secure, Path=/, отсутствие Domain | Более строгая привязка к хосту и пути. |
__Secure- | Secure | Защита от отправки по HTTP. |
Пример безопасного сессионного куки:
Set-Cookie: __Host-sessionid=abc123; Secure; HttpOnly; SameSite=Lax; Max-Age=3600; Path=/
🔹 Кэширование: продвинутые сценарии
Валидация и обновление
| Сценарий | Запрос клиента | Ответ сервера | Результат |
|---|
| Свежий кэш | — | Cache-Control: max-age=3600, ETag: "abc" | Кэш используется (возраст < 3600). |
| Устаревший → валидация | If-None-Match: "abc" | 304 Not Modified, ETag: "abc", Cache-Control: max-age=3600 | Кэш обновлён (свежесть = 3600 с момента ответа). |
| Устаревший → изменён | If-None-Match: "abc" | 200 OK, ETag: "def", Cache-Control: max-age=3600 | Кэш заменён. |
Устаревший + must-revalidate | — | Cache-Control: max-age=3600, must-revalidate | При истечении — обязательно If-None-Match. |
stale-while-revalidate и stale-if-error
| Директива | Поведение |
|---|
stale-while-revalidate=60 | Можно отдавать устаревший контент, пока в фоне идёт валидация (до 60 сек). |
stale-if-error=86400 | При ошибке сервера (5xx) можно отдавать устаревший контент (до 1 дня). |
Пример для CDN:
Cache-Control: public, max-age=60, s-maxage=300, stale-while-revalidate=60, stale-if-error=86400
🔹 Соединения и транспорт
| Заголовок/Параметр | RFC | Пояснение |
|---|
Connection: keep-alive | HTTP/1.1 по умолчанию | Сохранение соединения для последующих запросов. |
Keep-Alive: timeout=5, max=1000 | Устаревший (HTTP/1.0) | timeout — секунд до закрытия, max — макс. запросов на соединение. |
Upgrade: h2c | RFC 7540 | HTTP/2 Cleartext (без TLS), редко используется. |
Alt-Svc | RFC 7838 | Альтернативные сервисы: Alt-Svc: h3=":443"; ma=3600, h2=":443"; ma=3600 |
Early-Data | RFC 8470 | Early-Data: 1 — запрос отправлен в 0-RTT TLS 1.3. Сервер может ответить 425 Too Early. |
🔹 HTTP/2 (RFC 9113) и HTTP/3 (RFC 9114) — ключевые отличия
| Фича | HTTP/1.1 | HTTP/2 | HTTP/3 |
|---|
| Версия | текстовая строка (HTTP/1.1) | PRI * HTTP/2.0\r\n\r\nSM\r\n\r\n → SETTINGS frame | QUIC (UDP), версия в TLS ALPN (h3) |
| Заголовки | текстовые, повторяются | HPACK-сжатие (Huffman + динамический словарь) | QPACK (асинхронный HPACK, безопасный от блокировок) |
| Мультиплексирование | нет (ограничение по 6 соединений/хост) | есть (streams, frames) | есть (streams в QUIC) |
| Приоритезация | нет | веса и зависимости (устарело в RFC 9113) | нет (оставлено приложениям) |
| Server Push | нет | есть (PUSH_PROMISE), устарело | удалено |
| Псевдозаголовки | нет | :method, :scheme, :authority, :path | те же |
| Потоковая обработка | чанки (Transfer-Encoding: chunked) | DATA frames | STREAM frames |
| TLS | опционально | рекомендуется (но h2c разрешён) | обязательно (QUIC встроен в TLS 1.3) |
| Потеря пакета | блокирует всё соединение | блокирует только один stream | не блокирует другие streams (QUIC) |
Псевдозаголовки (HTTP/2, HTTP/3):
:method — метод (обязателен в запросе)
:scheme — http/https (обязателен)
:authority — аналог Host (обязателен; заменяет Host)
:path — URI-путь + query (обязателен)
:status — статус-код (в ответе)
HTTP/3 особенности:
- Порт по умолчанию — 443 (UDP).
- Поддержка 0-RTT (early data), но с риском replay →
425 Too Early.
Alt-Svc используется для миграции с HTTP/2 на HTTP/3.
🔹 Трассировка и мониторинг
1. Server-Timing (W3C Recommendation, 2019)
Передача метрик производительности от сервера клиенту (браузеру или мониторинговой системе).
Синтаксис
Server-Timing: [metric-name][=metric-value][;desc="description"][, ...]
metric-name — токен (например, db, cache, app).
metric-value — неотрицательное число (по умолчанию 0).
desc — строка в кавычках (опционально, для пояснения).
Примеры
Поддержка
- Браузеры: Chrome ≥60, Firefox ≥60, Edge ≥79.
- Отображается в DevTools → Network → Timing → "Server Timing".
- Доступен через JavaScript:
performance.getEntriesByType('navigation')[0].serverTiming
Рекомендации
- Измерять этапы:
db, cache, auth, serialization, total.
- Не включать чувствительные данные в
desc.
- Для микросервисов — агрегировать или проксировать без дублирования имён.
2. Reporting API (RFC 9260)
Единый механизм отправки отчётов о проблемах (CSP, NEL, deprecation, intervention, crash).
Report-To
Объявляет endpoint’ы для отчётов. Устанавливается в ответе.
Синтаксис (JSON)
group — имя группы (должно совпадать с report_to в других заголовках).
max_age — срок жизни конфигурации (в секундах).
endpoints — массив URL’ов (поддерживается fallback).
include_subdomains — применять к поддоменам.
Типы отчётов
| Тип | Источник | Пример payload |
|---|
| CSP | Content-Security-Policy: ...; report-to=default | { "csp-report": { "document-uri": "...", "violated-directive": "script-src", ... } } |
| NEL | NEL: { "report_to": "default", "max_age": 86400 } | { "age": 120, "type": "http", "url": "...", "status_code": 500, "elapsed_time": 300, ... } |
| Deprecation | Браузер | { "type": "deprecation", "url": "...", "id": "PrefixedWebSocket", ... } |
| Intervention | Браузер | { "type": "intervention", "url": "...", "id": "AudioContextAutoplay", ... } |
| Crash | Браузер (экспериментально) | { "type": "crash", ... } |
NEL (Network Error Logging) — логирует сетевые ошибки (DNS failure, TCP timeout, TLS handshake fail), недоступные через JS.
Требования к endpoint’у
- Должен принимать
POST с Content-Type: application/reports+json.
- Возвращать
200 OK (иначе клиент повторит).
- Обрабатывать батчи (массив отчётов в одном теле).
🔹 Безопасность: углублённый разбор
1. Content Security Policy (CSP Level 3)
Контроль источников выполнения и загрузки ресурсов.
Синтаксис
Ключевые директивы
| Директива | Назначение | Пример |
|---|
default-src | fallback для всех *-src, кроме frame-ancestors, form-action, base-uri, sandbox | default-src 'self' |
script-src | источники скриптов | script-src 'self' https://cdn.example.com 'unsafe-inline' |
style-src | источники стилей | style-src 'self' 'unsafe-inline' |
img-src | изображения | img-src * data: blob: |
font-src | шрифты | font-src 'self' https://fonts.gstatic.com |
connect-src | fetch, XHR, WebSocket, EventSource | connect-src 'self' https://api.example.com |
frame-src | <iframe>, <frame> | frame-src 'none' |
frame-ancestors | кто может встроить страницу (<iframe>, <object>, <embed>) | frame-ancestors 'self' https://trusted.com |
form-action | куда можно отправлять формы | form-action 'self' |
base-uri | допустимые значения <base href> | base-uri 'self' |
object-src | <object>, <embed>, <applet> | object-src 'none' |
worker-src | Worker, SharedWorker | worker-src 'self' blob: |
manifest-src | Web App Manifest | manifest-src 'self' |
media-src | <audio>, <video> | media-src * |
prefetch-src | rel=prefetch, prerender | prefetch-src https://cdn.example.com |
report-to / report-uri | отправка отчётов | report-to default |
Источники (source expressions)
| Выражение | Пояснение |
|---|
'self' | тот же origin (scheme, host, port) |
https: | любой HTTPS-ресурс |
*.example.com | поддомены |
'unsafe-inline' | inline-скрипты/стили (избегать) |
'unsafe-eval' | eval(), new Function() (избегать) |
'nonce-<base64>' | разрешить скрипт/стиль с nonce="<base64>" |
'sha256-<base64>' | хэш содержимого (только для inline) |
data: | data: URL |
blob: | Blob URL |
'strict-dynamic' | доверять только динамически созданным скриптам (с nonce/hash) |
Режимы
- enforce (
Content-Security-Policy) — блокирует нарушения.
- report-only (
Content-Security-Policy-Report-Only) — только логирует.
Рекомендации:
- Начинать с
report-only, собирать отчёты, анализировать, затем включать enforce.
- Избегать
'unsafe-inline', 'unsafe-eval'.
- Использовать
nonce или hash для inline-контента.
- Указывать
object-src 'none', base-uri 'self', form-action 'self' по умолчанию.
2. Изоляция: COOP, COEP, CORP
| Заголовок | RFC | Значение | Эффект |
|---|
Cross-Origin-Opener-Policy: same-origin | RFC 9675 | Запрет доступа к window.opener из кросс-сайтовых окон | Защита от XS-Leaks, включение SharedArrayBuffer |
Cross-Origin-Embedder-Policy: require-corp | RFC 9675 | Все embed’ы (<script>, <img>, fetch()) должны иметь CORS или Cross-Origin-Resource-Policy | Требуется для SharedArrayBuffer, предотвращает side-channel атаки |
Cross-Origin-Resource-Policy: same-origin | RFC 9675 | Ресурс может быть загружен только с того же origin’а | Защита от встраивания в кросс-сайтовые страницы |
Требования для SharedArrayBuffer
Cross-Origin-Opener-Policy: same-origin
Cross-Origin-Embedder-Policy: require-corp
- Все сторонние ресурсы — с CORS или
CORP: same-site/same-origin.
3. Clear-Site-Data
Очистка данных при logout или уничтожении сессии.
Синтаксис
"cache" — HTTP-кэш
"cookies" — все куки для origin’а
"storage" — localStorage, sessionStorage, IndexedDB, Cache API
"executionContexts" — закрытие всех вкладок/воркеров для origin’а
"*" — всё вышеперечисленное
Пример
Ограничения:
- Работает только по HTTPS.
- Не удаляет Service Worker (требуется явный
serviceWorker.unregister()).
executionContexts — поддержка ограничена.
4. Permissions-Policy (бывший Feature-Policy)
Контроль над powerful API браузера.
Синтаксис
Примеры
Часто отключаемые фичи
| Фича | Опасность |
|---|
sync-xhr | блокирующие запросы → плохой UX |
document-domain | ослабление SOP → уязвимости |
picture-in-picture | UX-спам |
usb, serial, hid | доступ к устройствам |
Совет: Отключайте всё по умолчанию, включайте выборочно.
🔹 Диагностика: типичные проблемы и как их выявить
| Проблема | Симптомы | Инструменты диагностики | Решение |
|---|
Некорректный Content-Type | JS не выполняется, JSON парсится как текст | DevTools → Network → Headers → Content-Type | Указать Content-Type: application/json; charset=utf-8 |
Отсутствует Vary | CDN отдаёт неверную версию (например, gzip без Accept-Encoding) | curl -H "Accept-Encoding: gzip" -I ... → сравнить Vary и тело | Добавить Vary: Accept-Encoding, Accept |
| CORS failure | fetch() → TypeError: Failed to fetch | DevTools → Console → CORS error; Network → Headers | Проверить Access-Control-Allow-Origin, Allow-Methods, Allow-Headers, Credentials |
| Куки не отправляются | Cookie отсутствует в запросе | DevTools → Application → Cookies; Network → Request Headers | Проверить Secure, SameSite, Domain, Path, HttpOnly (не влияет на отправку) |
| Сессия «теряется» | Пользователь разлогинивается при переходе | Логи сервера, Set-Cookie в ответах | Убедиться, что Domain, Path согласованы; нет SameSite=Strict в кросс-сайтовых POST |
| Кэш не обновляется | Старый JS/CSS после деплоя | DevTools → Network → Disable cache (временно); curl -H "Cache-Control: no-cache" -I ... | Добавить хэш в имя файла (app.a1b2c3.js), Cache-Control: immutable |
| HTTP/2 push не работает | PUSH_PROMISE не виден | nghttp -v https://..., chrome://net-internals/#http2 | Убедиться, что сервер поддерживает push; браузер не отключил (chrome://flags/#enable-http2-push) |
425 Too Early | Запросы падают при TLS 1.3 0-RTT | Логи сервера, curl --early-data ... | Сервер должен возвращать 425, клиент — повторять без early data |
🔹 Инструменты для работы с HTTP
| Инструмент | Назначение | Примеры использования |
|---|
curl | Отправка HTTP-запросов, отладка | |
curl -v -H "Accept: application/json" https://api.example.com | | |
curl -X POST -d '{"key":"value"}' -H "Content-Type: application/json" ... | | |
curl --compressed -H "Accept-Encoding: br,gzip" ... | | |
nghttp / nghttp2 | HTTP/2 CLI-клиент/сервер | |
nghttp -nv https://http2.example.com — verbose, заголовки, фреймы | | |
nghttp -u https://... — upgrade to H2C | | |
h2spec | Тестирование совместимости с HTTP/2 | |
h2spec -k -p 443 example.com — проверка сервера на соответствие RFC | | |
| Wireshark / tshark | Анализ сетевого трафика | |
Фильтр: http2, tls.handshake.type == 1, http.request.method == "POST" | | |
| Декодирование HPACK/QPACK (требует ключи TLS для расшифровки) | | |
| DevTools (Chrome/Firefox) | Отладка в браузере | |
| Network → Headers, Timing, Initiator, Waterfall | | |
| Application → Cookies, Cache Storage | | |
| Security → Certificate, CSP, COOP/COEP | | |
mitmproxy | Прокси для инспекции и модификации трафика | |
| Перехват HTTPS (требует установки CA), редактирование запросов/ответов, скрипты на Python | | |
httpstat | Визуализация времени запроса (аналог curl -w) | |
httpstat https://example.com → DNS, TCP, TLS, TTFB, total | | |
hey / wrk / k6 | Нагрузочное тестирование | |
hey -n 10000 -c 100 -H "Authorization: Bearer ..." https://api.example.com | | |